# -*- coding: utf-8 -*-
# -*- frozen_string_literal: true -*-
require_relative "./../../../_config/minitest"
require "lorca/expansions/cli"

class FakeOutlet
  def tty?
    true
  end

  def puts text
    $stdout.puts text
  end
end

class TestLorcaCLIExpansion < Minitest::Test

  # test dependencies, useful for testing Lorca::CLI but should be replaceable
  require "lorca"
  require "clipboard" # Lorca can't paste, nor clear, clipboard contents

  def setup
    @argv = -> options { Array[StringIO.new(options).read.split] }
    @cli = Object.new.extend Lorca::CLI
  end

  def test_display_help_when_no_options_given
    assert_output(%r"\Ausage"i) { @cli.parse @argv.("") }
  end

  def test_h__help_shows_usage_info
    assert_output(%r"\Ausage"i) { @cli.parse @argv.("-h") }
    assert_output(%r"\Ausage"i) { @cli.parse @argv.("--help") }
  end

  def test_p__phrase_copies_passphrase_to_clipboard
    writer = Lorca.add(Lorca::Phrases).new
    message = %r"\Apassphrase copied to clipboard\n"i # no `\z` due to `exit_cli`
    copied = "ah"
    outlet = FakeOutlet.new

    writer.stub :phrase, copied do
      assert_output(message) { @cli.parse @argv.("--phrase"), writer: writer, outlet: outlet }
      assert_output(message) { @cli.parse @argv.("-p"), writer: writer, outlet: outlet }
    end

    assert_equal copied, Clipboard.paste
    Clipboard.clear
  end

  def test_phrase_flag_can_take_an_optional_number_argument
    writer = Lorca.add(Lorca::Phrases).new
    copied = "ah"
    outlet = FakeOutlet.new

    writer.stub :phrase, copied do
      _ = capture_io { @cli.parse @argv.("--phrase 9"), writer: writer, outlet: outlet }
      assert_equal copied, Clipboard.paste
    end
    Clipboard.clear
  end

  def test_phrase_can_be_streamed
    writer = Lorca.add(Lorca::Phrases).new
    copied = "ah"

    writer.stub :phrase, copied do
      assert_output(%r"\Aah") { @cli.parse @argv.("--phrase"), writer: writer }
      assert_output(%r"\Aah") { @cli.parse @argv.("-p"), writer: writer }
    end
  end

  def test__version_displays_lorca_version
    assert_output(%r"\A#{Lorca::LorcaVersion}") { @cli.parse @argv.("--version") }
  end
end

class TestCLILorcaPlugin < Minitest::Test
  def test_lorca_cli_plugin
    argv = -> options { Array[StringIO.new(options).read.split] }
    lorca = Lorca.add(Lorca::CLI).new

    assert_output(%r"\Ausage"i) { lorca.run argv.("") }
  end
end
